package com.atguigu.linkedlist;

/**
 * @author durant
 * @create 2021-11-12 11:08
 */
public class Josepfu {
    public static void main(String[] args) {
        CircleSingleLinkedList list=new CircleSingleLinkedList();
        list.addBoy(5);
        System.out.println("开始报数");
        list.countBoy(3, 2, 5);
    }
}

class CircleSingleLinkedList {
    private BoyNode first = new BoyNode(1);

    //添加小孩的节点，构建环形链表

    public void addBoy(int num) {
        if (num < 1) {
            System.out.println("num值不正确");
            return;
        }
        //辅助节点，帮助循环
        BoyNode current = null;
        //创建环形链表
        for (int i = 1; i <= num; i++) {
            BoyNode boy = new BoyNode(i);
            //构建第一个小孩
            if (i == 1) {
                first = boy;
                current=first;
                current.setNext(first);
            } else {
                current.setNext(boy);
                boy.setNext(first);
                current = boy;
            }

        }

    }
    //遍历当前的环形链表
    public void list(){
        //判断链表是否为空
        if (first == null){
            System.out.println("链表为空");
        }
        //使用辅助指针进行遍历
        BoyNode current= first;
        while (true){
            System.out.println("小孩的编号："+current.getNo());
            if (current.getNext().getNo() == first.getNo()){
                break;
            }
            current=current.getNext();
        }
    }
    /*
    @Description
    *
     * @param startNo   开始的小孩索引
     * @param countNum   表示数几下
     * @param nums       表示最初有几个小孩在圈中
    *@Author Mr.Ren
    *@Date 2021/11/12
    *@Time 12:26
    */
    public void countBoy(int startNo,int countNum,int nums){
        //需要辅助指针，指向要删除节点的后面
        //由于first指针指在第一个，所以设定辅助指针在最后一个即第一个的后面一个
        //进行遍历，同增加，这样first指针遍历到的节点需要删除，可以通过辅助指针的next指定first的下一个
        if (countNum<1 || first ==null || startNo > nums){
            System.out.println("参数输入有误，请重新输入");
            return;
        }
        BoyNode helper=first;// 创建一个helper辅助变量，指向环形链表的最后节点
        while (true){
            if (helper.getNext() == first){//
                break;
            }
            helper=helper.getNext();
        }
        // 在报数之前，应该移动到指针应该在的地方
        while (true){
            if (first.getNo() ==  startNo){
                break;
            }
            first=first.getNext();
            helper=helper.getNext();
        }
        // 移动到指定位置后，开始报数
        // 同时移动countnum - 1个位置,
        while (true){
            for (int i = 0; i < countNum-1; i++) {
                first=first.getNext();
                helper=helper.getNext();
            }
            //移动到指定位置，开始输出
            System.out.println("小孩的位置："+first.getNo());
            //first 下移一位

            first=first.getNext();
            helper.setNext(first);
            if (first.getNext().getNo() == helper.getNo()){
                System.out.println("小孩的位置："+first.getNo());
                System.out.println("小孩的位置："+helper.getNo());
                break;
            }
        }
    }

}

class BoyNode {
    private int no;
    private BoyNode next;//指向下一个节点

    public BoyNode getNext() {
        return next;
    }

    public void setNext(BoyNode next) {
        this.next = next;
    }

    public int getNo() {

        return no;
    }


    public void setNo(int no) {
        this.no = no;
    }

    public BoyNode(int no) {
        this.no = no;
    }
}
